/*!Cette classe définit un automate. Un automate est défini par un ensemble d'objets de type etat. Elle ne possède qu'un affichage en mode texte, il est donc assez difficile de voir ce qu'elle fait*/

#ifndef H_automate
#define H_automate

#include "../Entetes/etat.h"
#include<string.h>

class automate{

	public :

		///tableau de pointeurs sur tous les états de l'automate
		std::vector<etat*> etats;

		/*!alphabet de travail : tableau des caractères pour lesquels il existe quelquepart une transition*/
		std::vector<bool> alphabet;

		///tableau de pointeurs sur les états finaux
		std::vector<etat*> etats_finaux;

		///pointeur sur l'état courant permettant le parcours de l'automate
		etat *etat_courant;

	public :

		///automate à un état vide
		automate();

		///constructeur par copie
		automate(const automate & at);

		/*testament*/
		//~automate();

		///automate à un état puits
		void automate_puits();

		///ajoute un état
		void automate_ajoute_etat(etat* et);

		///ajoute un état final
		void automate_ajoute_final(etat* et, int code);

		///ajoute une transition entre l'état precedent et suivant
		void ajoute_transition(etat* precedent, etat* suivant, unsigned char caract);

		///ajoute une epsilon-transition entre l'état precedent et suivant
		void ajoute_epsilon_transition(etat* precedent, etat* suivant);
		
		/*!met à jour l'ensemble des transitions entre les états precedent et suivant*/
		void ajoute_transitions(etat* precedent, etat* suivant, transitions trans);
		
		/*!renvoie l'automate qui reconnaît l'expression régulière A* si aut reconnait A. Laisse aut inchangé*/
		automate& plus(automate *aut);

		/*!renvoie l'automate qui reconnaît l'expression régulière A? si aut reconnait A. Laisse aut inchangé*/
		automate& interrog(automate *aut);
		
		/*!renvoie l'automate qui reconnaît l'expression régulière A? si aut reconnait A. Laisse aut inchangé*/
		automate& etoile(automate *aut);

		/*!renvoie l'automate qui reconnaît l'expression régulière A ou l'expression régulière B si aut1 reconnait A et aut2 B. Laisse aut1 et aut2 inchangés*/
		automate& addition(automate *aut1, automate *aut2);

		/*!renvoie l'automate qui reconnaît l'expression régulière AB si aut1 reconnait A et aut2 B. Laisse aut1 et aut2 inchangés*/
		automate& concatenation(automate *aut1, automate *aut2);

		///affichage de l'automate, mais là encore, c'est pas du tout de qu'on croit
		void affichage();
};

#endif
